import Cesium from 'cesium';

class SlopeMeasure {
  handler:any;
  id:any;
  viewer:any;
  helperTips:any;
  pointArr:any;
  entitiesArr:any;

  constructor(viewer:any) {
    //鼠标事件
    this.handler = new Cesium.ScreenSpaceEventHandler(viewer.scene.canvas);
    this.id = Cesium.createGuid();
    this.viewer = viewer;
    this._tip = viewer.entities.add({
      id: this.id,
      label: {
        //name: 'visiblyEffect',
        //show : false,
        fillColor: Cesium.Color.YELLOW,
        showBackground: true,
        font: '14px monospace',
        horizontalOrigin: Cesium.HorizontalOrigin.LEFT,
        verticalOrigin: Cesium.VerticalOrigin.BOTTOM,
        pixelOffset: new Cesium.Cartesian2(0, -10),
        // heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
      }
    });
    this.pointArr = [];
    //所有的实体
    this.entitiesArr = [];
  }

  /**
   * 初始化-鼠标mouse提示和点击中心点
   * @param radius  半径范围
   * @param yjSlope  预警坡度
   * @param wxSlope  威胁坡度
   */
  startAnalysis(radius:number, yjSlope:any, wxSlope:any) {
    this.pointArr = [];
    var _this = this;
    var info = "";
    // this.viewer.scene.globe.depthTestAgainstTerrain = true;
    if (!this.handler) {
      this.handler = new Cesium.ScreenSpaceEventHandler(this.viewer.scene.canvas);
    }
    _this.createHelper([-1000,-1000], info);
    //移动-主要是文字提示
    _this.handler.setInputAction(function (movement:any) {
      info = '左键点击绘制两点成线';
      _this.updateHelper(movement.position,info)
    }, Cesium.ScreenSpaceEventType.MOUSE_MOVE);

    //点击-添加点-进行分析
    _this.handler.setInputAction(function (movement:any) {
      var cartesian = _this.viewer.scene.pickPosition(movement.position);
      let cartographic = Cesium.Cartographic.fromCartesian(cartesian, _this.viewer.scene.globe.ellipsoid, new Cesium.Cartographic());
      let lat = Cesium.Math.toDegrees(cartographic.latitude);
      let lng = Cesium.Math.toDegrees(cartographic.longitude);
      let height = cartographic.height;
      _this.pointArr.push({
        x: lng,
        y: lat,
        z: height
      });
      if (_this.pointArr.length == 2) {
        _this.handler.removeInputAction(Cesium.ScreenSpaceEventType.LEFT_CLICK);
        _this.handler.removeInputAction(Cesium.ScreenSpaceEventType.MOUSE_MOVE);
        _this.removeHelper();
        _this.CalculateSlope(_this.pointArr);
      }
    }, Cesium.ScreenSpaceEventType.LEFT_CLICK);
  }
  /**
   * 计算坡度值-勾股定理-
   * 角度 = 弧度 * 180 / Math.PI
   * @create zgf
   * @constructor
   */
  CalculateSlope(pointsArr:Array<any>) {
    var startPoint = pointsArr[0];
    var endPoint = pointsArr[1];
    var sinValue = (endPoint.z - startPoint.z) /
      Cesium.Cartesian3.distance(
        Cesium.Cartesian3.fromDegrees(startPoint.x, startPoint.y, startPoint.z),
        Cesium.Cartesian3.fromDegrees(endPoint.x, endPoint.y, endPoint.z)
      );
    // 根据sin得到弧度值
    var radian = Math.asin(sinValue);
    var angle = radian * 180 / Math.PI;
    // 坡向
    var sapect = this.CalculateAspect(startPoint, endPoint);
    this.addSlopeEntity(startPoint, endPoint, angle.toFixed(2), sapect.toFixed(2));
  }

  /**
   * 计算坡向-
   * {坡向为坡度线在水平面的投影与整备方向的夹角，从整北方向开始，顺时针，范围0-360}
   * 角度 = 弧度 * 180 / Math.PI
   * @create zgf
   * @constructor
   */
  CalculateAspect(startPoint:any, endPoint:any) {
    //平移中心点至(0,0)
    var zeroPoint = {
      x: endPoint['x'] - startPoint['x'],
      y: endPoint['y'] - startPoint['y']
    }
    //弧度值
    var hd = Math.abs(Math.atan(zeroPoint['y'] / zeroPoint['x']));
    var jd = hd * 180 / Math.PI;
    var px = null;
    if (zeroPoint['x'] > 0 && zeroPoint['y'] > 0) {
      px = 90 - jd;
    } else if (zeroPoint['x'] < 0 && zeroPoint['y'] > 0) {
      px = 270 + jd;
    } else if (zeroPoint['x'] < 0 && zeroPoint['y'] < 0) {
      px = 270 - jd;
    } else if (zeroPoint['x'] > 0 && zeroPoint['y'] < 0) {
      px = 90 + jd;
    }
    return px;
  }
  addSlopeEntity(startPoint:any, endPoint:any, angle:any, sapect:any) {
    var startCartesian3 = Cesium.Cartesian3.fromDegrees(startPoint['x'], startPoint['y'], startPoint['z'] + 2);
    var endCartesian3 = Cesium.Cartesian3.fromDegrees(endPoint['x'], endPoint['y'], endPoint['z'] + 2);
    var middleCartesian3 = Cesium.Cartesian3.fromDegrees(
      (endPoint['x'] + startPoint['x']) / 2,
      (endPoint['y'] + startPoint['y']) / 2,
      ((endPoint['z'] + startPoint['z']) / 2) + 10);
    //添加箭头实体
    var en = this.viewer.entities.add({
      // id:Date.parse(new Date())+'single-slope',
      polyline: {
        positions: [startCartesian3, endCartesian3],
        width: 10,
        arcType: Cesium.ArcType.NONE,
        material: new Cesium.PolylineArrowMaterialProperty(Cesium.Color.RED),
        // clampToGround :true, //折线贴地
      }
    });
    this.entitiesArr.push(en);
    var text = angle < 0 ? "-" + Math.abs(angle) : Math.abs(angle) + "";
    text = "坡度:" + text + "°; 坡向:" + sapect + "°";
    //添加文字实体
    var label = this.viewer.entities.add({
      position: middleCartesian3,
      point: { //点
        pixelSize: 1,
        color: new Cesium.Color(0.0, 0.0, 0.0, 0.0) //颜色设置透明
        // heightReference:Cesium.HeightReference.CLAMP_TO_GROUND,
      },
      label: { //文字标签
        text: text + "",
        font: '14pt monospace',
        style: Cesium.LabelStyle.FILL_AND_OUTLINE,
        fillColor: Cesium.Color.RED,
        outlineColor: Cesium.Color.WHITE,
        outlineWidth: 5,
        verticalOrigin: Cesium.VerticalOrigin.BOTTOM, //垂直方向以底部来计算标签的位置
        pixelOffset: new Cesium.Cartesian2(0, -25), //偏移量
        // heightReference:Cesium.HeightReference.CLAMP_TO_GROUND,
      },
    });
    this.entitiesArr.push(label);
  }

  /**
   * 提示框
   * @param {*} label
   * @param {*} bShow
   * @param {*} position
   * @param {*} message
   * @param {*} effectOptions
   */
  showTip(label:any, bShow:any, position:any, message:any, effectOptions:any) {
    label.show = bShow;
    if (bShow) {
      if (position)
        label.position = position;
      if (message)
        label.label.text = message;
      if (effectOptions) {
        for (let key in effectOptions) {
          if (label.key) {
            label.key = effectOptions[key];
          }
        }
      }
    }
  }

  /**
   * 移除当前添加的坡度实体
   * @create zgf
   */
  disponse() {
    if (this.entitiesArr.length == 0) {
      return;
    }
    for (let index = 0; index < this.entitiesArr.length; index++) {
      var element = this.entitiesArr[index];
      this.viewer.entities.remove(element);
    }
  }

  /**
   * 创建文字提示
   * @param screenPosition
   * @param text
   */
  createHelper(screenPosition: any, text: string) {
    this.helperTips = document.createElement('div');
    this.helperTips.innerText = text;
    this.helperTips.style.color = '#00FA9A';
    this.helperTips.style.position = 'fixed';
    this.helperTips.style.left = screenPosition['x'] + 'px';
    this.helperTips.style.top = screenPosition['y'] + 20 + 'px';
    this.helperTips.style.backgroundColor = '#FFFFFF';
    document.body.appendChild(this.helperTips);
  }

  /**
   * 更新文字提示
   * @param screenPosition
   * @param text
   */
  updateHelper(screenPosition: any, text: string) {
    this.helperTips.style.left = screenPosition['x'] + 'px';
    this.helperTips.style.top = screenPosition['y'] + 20 + 'px';
    this.helperTips.innerText = text;
  }

  removeHelper() {
    if(this.helperTips){
      this.helperTips.remove();
    }
  }


}
export default SlopeMeasure;
